package com.yanqu.road.server.manger.activity.snowgarden;

import com.yanqu.road.entity.activity.ActivityConfig;
import com.yanqu.road.entity.activity.ActivityInfo;
import com.yanqu.road.entity.activity.UserActivityConditionData;
import com.yanqu.road.entity.activity.snowgarden.*;
import com.yanqu.road.entity.activity.snowgarden.config.*;
import com.yanqu.road.entity.config.goods.GoodsInfo;
import com.yanqu.road.entity.enums.activity.snowgarden.eSnowGardenMapType;
import com.yanqu.road.entity.enums.activity.snowgarden.eSnowGardenPeriodType;
import com.yanqu.road.entity.enums.activity.snowgarden.eSnowGardenRequestVisitType;
import com.yanqu.road.entity.enums.activity.snowgarden.eSnowGardenVisitType;
import com.yanqu.road.entity.enums.eActivityType;
import com.yanqu.road.entity.enums.eGamePlayerEventType;
import com.yanqu.road.entity.player.UserBaseInfo;
import com.yanqu.road.entity.player.UserInfo;
import com.yanqu.road.entity.union.cross.CrossUnionMember;
import com.yanqu.road.logic.bussiness.activity.SnowGardenBusiness;
import com.yanqu.road.logic.pb.PlayerBasePb;
import com.yanqu.road.logic.thread.ThreadTaskManger;
import com.yanqu.road.pb.activity.SnowGardenProto;
import com.yanqu.road.server.TempMgr;
import com.yanqu.road.server.game.service.GameService;
import com.yanqu.road.server.gameplayer.GamePlayer;
import com.yanqu.road.server.gameplayer.module.activity.snowgarden.SnowGardenModule;
import com.yanqu.road.server.manger.activity.ActivityMgr;
import com.yanqu.road.server.manger.activity.NormalActivityMgr;
import com.yanqu.road.server.manger.activity.snowgarden.service.SnowGetUserVisitDataCmdService;
import com.yanqu.road.server.manger.activity.snowgarden.task.SnowGardenVisitTask;
import com.yanqu.road.server.manger.config.BeautyMgr;
import com.yanqu.road.server.manger.config.PatronsMgr;
import com.yanqu.road.server.manger.player.GamePlayerMgr;
import com.yanqu.road.server.manger.player.UserMgr;
import com.yanqu.road.server.manger.rank.ActivityRankMgr;
import com.yanqu.road.server.manger.system.CommonMgr;
import com.yanqu.road.server.manger.union.CrossUnionMgr;
import com.yanqu.road.server.pb.SnowGardenPb;
import com.yanqu.road.server.protocol.CrossProtocol;
import com.yanqu.road.server.protocol.GameErrorCode;
import com.yanqu.road.server.protocol.GameProtocol;
import com.yanqu.road.utils.RandomHelper;
import com.yanqu.road.utils.YanQuMessageUtils;
import com.yanqu.road.utils.property.Property;
import com.yanqu.road.utils.property.PropertyHelper;
import com.yanqu.road.utils.string.StringUtils;

import java.math.BigDecimal;
import java.math.BigInteger;
import java.math.RoundingMode;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;

public class SnowGardenMgr extends TempMgr {

    private static SnowGardenConfig snowGardenConfig;

    private static Map<Integer, Map<Long, Map<Integer, List<UserActivityConditionData>>>> userActivityConditionDataMap;

    // 投掷结果最大数量
    private static final int resultNum = 9;

    private static ThreadTaskManger threadTaskManger;
    private static Random random = new Random();

    private static Map<Integer, CacheSnowDataActivity> cacheSnowDataActivityMap = new ConcurrentHashMap<>();
    // 骰子点数设置(一阶段6点，二阶段5职业)
    public static final int rollNum = 6;
    public static final int secondRollNum = 5;


    @Override
    public boolean init() throws Exception {
        return reload();
    }

    @Override
    public boolean reloadConfig() throws Exception {
        return true;
    }

    @Override
    public boolean reloadData() throws Exception {
        if (null == threadTaskManger) {
            threadTaskManger = new ThreadTaskManger(1, "SnowGardenMgr");
        }
        return true;
    }

    @Override
    public boolean stop() {
        return true;
    }

    @Override
    public boolean save() {
        for (CacheSnowDataActivity activity : cacheSnowDataActivityMap.values()) {
            activity.save();
        }

        return true;
    }

    public static void initService(GameService syncMessageService) {
        syncMessageService.addGameServiceCommand(GameProtocol.S_SNOW_GET_USER_VISIT_DATA_FROM_GAME, new SnowGetUserVisitDataCmdService());
    }

    public static void reloadActivityData() {
        getLogger().info("reload SnowGarden begin");

        // 拿活动数据
        List<ActivityInfo> list = NormalActivityMgr.getOpenActivityInfoList(eActivityType.SnowGarden.getValue());
        if (list.isEmpty()) {
            snowGardenConfig = null;
            cacheSnowDataActivityMap = new ConcurrentHashMap<>();
            getLogger().info("reload SnowGarden finish, no activity in show time.");
            return;
        }
        ActivityInfo activityInfo = list.get(0);
        int activityId = activityInfo.getActivityId();

        Map<String, ActivityConfig> configMap = NormalActivityMgr.getActivityConfigMap(activityId);

        // 初始化活动配置
        SnowGardenConfig config = new SnowGardenConfig();
        config.setActivityInfo(activityInfo);
        config.initActivityConfig(configMap);
        config.setSnowGardenCombConfig(SnowGardenBusiness.getSnowGardenCombConfig(activityId));
        config.setSnowGardenDollConfig(SnowGardenBusiness.getSnowGardenDollConfig(activityId));
        config.setSnowGardenLevelConfig(SnowGardenBusiness.getSnowGardenLevelConfig(activityId));
        config.setSnowGardenStatueConfig(SnowGardenBusiness.getSnowGardenStatueConfig(activityId));
        config.setSnowGardenMapConfig(SnowGardenBusiness.getSnowGardenMapConfig(activityId));
        // 游客表过滤一下不存在的id
        Set<Integer> patronsIdList = PatronsMgr.getPatronsInfoMap().keySet();
        Set<Integer> beautyIdList = BeautyMgr.getBeautyInfoMap().keySet();
        Map<Integer, SnowGardenVisitorConfig> visitorConfig = SnowGardenBusiness.getSnowGardenVisitorConfig(activityId);
        Map<Integer, SnowGardenVisitorConfig> newConfigMap = new ConcurrentHashMap<>();
        for(int key:visitorConfig.keySet()){
            int visitorId = visitorConfig.get(key).getVisitorId();
            if(patronsIdList.contains(visitorId) || beautyIdList.contains(visitorId)){
                newConfigMap.put(key, visitorConfig.get(key));
            }
        }
        config.setSnowGardenVisitorConfig(newConfigMap);
        config.setSnowGardenShowConfig(SnowGardenBusiness.getSnowGardenShowConfig(activityId));

        setSnowGardenConfig(config);

        getCacheSnowDataActivity(activityId);

        for (GamePlayer player : GamePlayerMgr.getAllOnlinePlayer()) {
            SnowGardenModule module = player.getModule(SnowGardenModule.class);
            module.initUserData();
            module.syncConfig();
            module.syncUserData();
        }
    }

    public static CacheSnowDataActivity getCacheSnowDataActivity(int activityId) {
        CacheSnowDataActivity cacheSnowDataActivity = cacheSnowDataActivityMap.get(activityId);
        if (cacheSnowDataActivity == null) {
            synchronized (cacheSnowDataActivityMap) {
                cacheSnowDataActivity = cacheSnowDataActivityMap.get(activityId);
                if (cacheSnowDataActivity == null) {
                    cacheSnowDataActivity = new CacheSnowDataActivity(activityId);
                    cacheSnowDataActivityMap.put(activityId, cacheSnowDataActivity);
                }
            }
        }
        return cacheSnowDataActivity;
    }


    public static ActivityInfo getActivityInfo() {
        return snowGardenConfig == null ? null : snowGardenConfig.getActivityInfo();
    }

    public static SnowGardenConfig getSnowGardenConfig() {
        return snowGardenConfig;
    }

    public static void setSnowGardenConfig(SnowGardenConfig snowGardenConfig) {
        SnowGardenMgr.snowGardenConfig = snowGardenConfig;
    }

    public static int getResultNum() {
        return resultNum;
    }


    public static Map<Integer, SnowGardenMapData> getInitMapData() {
        Map<Integer, SnowGardenMapData> newMapData = new HashMap<>();
        SnowGardenConfig config = getSnowGardenConfig();
        if (config == null) {
            return newMapData;
        }
        Map<Integer, SnowGardenMapConfig> mapConfig = config.getSnowGardenMapConfig();
        for (Integer key : mapConfig.keySet()) {
            SnowGardenMapData snowGardenMapData = new SnowGardenMapData();
            snowGardenMapData.setBuildingID(mapConfig.get(key).getStatueId());
            newMapData.put(key, snowGardenMapData);
        }
        return newMapData;
    }

    /**
     * 构造一份新数据
     */
    public static SnowGardenUserData createUserData(long userId) {
        SnowGardenConfig config = getSnowGardenConfig();

        // 初始化角色数据
        SnowGardenUserData userData = new SnowGardenUserData(config.getActivityInfo().getActivityId(), userId);
        userData.setActivityId(config.getActivityInfo().getActivityId());
        userData.setUserId(userId);

        // 初始第一圈第0格位置
        int period = calcNowPeriod();
        userData.setPeriod(period);
        userData.setLoopNum(0);
        userData.setIndexNum(1);
        userData.setIndexData(getInitMapData());

        List<Integer> resultList = initResultList();
        userData.setResultList(resultList);

        // 初始化默认外观
        int initSuitId = config.getInitSuitId();
        userData.setSuit(initSuitId);
        SnowGardenSkinData initSkinData = new SnowGardenSkinData(initSuitId, -1, true);
        Map<Integer, SnowGardenSkinData> initSkinList = new ConcurrentHashMap<>();
        initSkinList.put(initSuitId, initSkinData);
        userData.setSkinList(initSkinList);


        userData.setInvitedIdList(new ArrayList<>());
        userData.setCombList(new ArrayList<>());
        userData.setGuarantee(randomGuarantee(period));
        userData.setDice(randomDice(period));

        return userData;
    }

    // 计算当前的阶段
    public static int calcNowPeriod() {
        SnowGardenConfig config = getSnowGardenConfig();
        long now = System.currentTimeMillis();
        if(now >= config.getPeriod1StartTime() && now <= config.getPeriod1EndTime()){
            return eSnowGardenPeriodType.UPGRADE_PERIOD.getType();
        } else if(now >= config.getPeriod2StartTime() && now <= config.getPeriod2EndTime()){
            return eSnowGardenPeriodType.VISITOR_PERIOD.getType();
        }
        return -1;
    }

    // 初始化结果列表
    public static List<Integer> initResultList(){
        List<Integer> list = new ArrayList<>(resultNum);
        for(int i = 0; i < resultNum;i++){
            list.add(i,0);
        }
        return list;
    }

    /**
     * 解析字符串转换时间
     */
    public static Calendar parseStringToDate(String s){
        List<String> Time = StringUtils.stringToStringList(s,"\\.");
        Calendar calendar = Calendar.getInstance();
        calendar.set(Calendar.YEAR, Integer.valueOf(Time.get(0)));
        calendar.set(Calendar.MONTH, Integer.valueOf(Time.get(1)) - 1);
        calendar.set(Calendar.DATE, Integer.valueOf(Time.get(2)));
        calendar.set(Calendar.HOUR_OF_DAY, Integer.valueOf(Time.get(3)));
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);
        return calendar;
    }

//    /**
//     * 获取玩家对象数据 不存在则创建对象
//     */
//    public static SnowGardenUserData getUserData(int activityId, long userId) {
//        SnowGardenUserData userData = SnowGardenBusiness.getSnowGardenUserData(activityId, userId);
//        if(userData == null){
//            userData = createUserData(userId);
//        }
//        return userData;
//    }

    // 拜访不在线玩家
//    public static String visitPlayer(long visitUserId, long targetUserId, int visitType, String visitParam, SnowGardenUserData userData, SnowGardenVisitorRecordData recordData){
//        int recordId;
//        String result;
//        int awardScore;
//        if (visitType == eSnowGardenRequestVisitType.BUILDING.getType()){
//            // 升级建筑 参数  地块_升级等级
//            List<Integer> paramList = StringUtils.stringToIntegerList(visitParam, "_");
//            recordId = paramList.get(0);
//            int randomStatue = SnowGardenMgr.getSnowGardenConfig().getSnowGardenMapConfig().get(recordId).getStatueId();
//            int oldLevel = userData.getIndexData().get(recordId).getLevel();
//            // 升级建筑 + 积分
//            int newLevel = oldLevel + paramList.get(1);
//            userData.getIndexData().get(recordId).setLevel(newLevel);
//            awardScore = SnowGardenMgr.getSnowGardenConfig().getSnowGardenStatueConfig().get(randomStatue).getScore()  * paramList.get(1);
//            result = String.format("%d_%d_%d", recordId, newLevel, awardScore);
//        } else if(visitType == eSnowGardenRequestVisitType.INVITED.getType()){
//            // 邀请 参数  游客id_积分倍率
//            List<Integer> paramList = StringUtils.stringToIntegerList(visitParam, "_");
//            recordId = paramList.get(0);
//            awardScore = SnowGardenMgr.getVisitorScoreById(recordId) * paramList.get(1);
//            userData.getInvitedIdList().add(recordId);
//            result = String.format("%d_%d", recordId, awardScore);
//        } else {
//            // 非指定上述类型拜访则不需要记录拜访数据,下发数据后返回
//            return "";
//        }
//        userData.addScore(awardScore);
//        if(SnowGardenMgr.getUserVisitData(userData.getActivityId(), targetUserId, eSnowGardenVisitType.VISIT_TYPE_VISITED_ME.getType()) == null) {
//            SnowGardenBusiness.addSnowGardenUserData(userData);
//        } else {
//            SnowGardenBusiness.updateSnowGardenUserData(userData);
//        }
//
//        // 更新离线玩家排行榜
//        RankMgr.changeActivityRank(userData.getActivityId(), targetUserId, BigInteger.valueOf((long)userData.getScore()), "");
//
//        SnowGardenVisitorRecord record = new SnowGardenVisitorRecord();
//        record.setId(recordId);
//        record.setType(visitType);
//        record.setTime((int)(System.currentTimeMillis() / 1000));
//        record.setUserId(visitUserId);
//        record.setScore(awardScore);
//        if(recordData != null) {
//            recordData.getRecordList().add(record);
//            setUserVisitData(targetUserId, eSnowGardenVisitType.VISIT_TYPE_VISITED_ME.getType(), recordData);
//        }
//        return result;
//    }

    /**
     * 获取玩家对象数据 不存在则创建对象
     */
//    public static SnowGardenVisitorRecordData getUserVisitData(int activityId, long userId, int type) {
//        GamePlayer player = GamePlayerMgr.getOnlinePlayer(userId);
//        SnowGardenVisitorRecordData userVisitData;
//        if(player == null){
//            userVisitData = SnowGardenBusiness.getSnowGardenVisitorRecord(activityId, userId, type);
//        } else {
//            userVisitData = player.getModule(SnowGardenModule.class).getSnowGardenVisitorRecordData().get(type);
//        }
//        return userVisitData;
//    }

//    /**
//     * 设置数据
//     */
//    public static void setUserVisitData(long userId, int type, SnowGardenVisitorRecordData userVisitData) {
//        GamePlayer player = GamePlayerMgr.getPlayer(userId);
//        if(player == null){
//            SnowGardenBusiness.updateSnowGardenVisitorRecord(userVisitData);
//        } else {
//            player.getModule(SnowGardenModule.class).getSnowGardenVisitorRecordData().put(type, userVisitData);
//        }
//    }
    public static int getVisitorScoreById(int visitorId) {
        Map<Integer, SnowGardenVisitorConfig> mapConfig = getSnowGardenConfig().getSnowGardenVisitorConfig();
        for (int key : mapConfig.keySet()) {
            if (mapConfig.get(key).getVisitorId() == visitorId) {
                return mapConfig.get(key).getScore();
            }
        }
        return 0;
    }

    // 传入地图数据，计算总等级获取对应增益倍率（千分比）
    public static int getLevelRadio(Map<Integer, SnowGardenMapData> indexData){
        // 建筑总等级
        int buildingLevel = 0;
        for(SnowGardenMapData d:indexData.values()){
            buildingLevel += d.getLevel();
        }
        Map<Integer, SnowGardenLevelConfig> levelConfig = snowGardenConfig.getSnowGardenLevelConfig();
        int returnRadio = 0;
        int configMaxLevel = 0;
        for(int key:levelConfig.keySet()){
            int configLevel = levelConfig.get(key).getLevel();
            if(configLevel < buildingLevel && configLevel >= configMaxLevel){
                returnRadio = levelConfig.get(key).getGain();
            }
        }
        return returnRadio;
    }

    // 按照config中的配置随机同品质任意门客
    public static int randomOneMoreVisitor(){
        Map<Integer, SnowGardenVisitorConfig> visitorConfig = snowGardenConfig.getSnowGardenVisitorConfig();
        int randomQuality = RandomHelper.getRandomKeyByWeight(snowGardenConfig.getVisitorParam());
        List<Integer> randomIdList = new ArrayList<>();
        for(int key:visitorConfig.keySet()){
            if(visitorConfig.get(key).getQuality() == randomQuality){
                randomIdList.add(key);
            }
        }
//        Random random = new Random();
        int index = random.nextInt(randomIdList.size());
        return randomIdList.get(index);
    }

    // 判断是否皮肤
    public static boolean isSkinItem(int goodsId){
        SnowGardenConfig config = getSnowGardenConfig();
        if(null == config){
            return false;
        }
        Map<Integer, SnowGardenDollConfig> dollConfigMap = config.getSnowGardenDollConfig();
        if(null == dollConfigMap){
            return false;
        }
        return dollConfigMap.containsKey(goodsId);
    }

    /**
     * 添加皮肤
     */
    public static void addSkin(GamePlayer player, int skinId, int count) {
        SnowGardenConfig config = getSnowGardenConfig();
        if (config == null){
            getLogger().error("玩家在活动时间外使用冰雪游园皮肤,userId = {}",player.getUserId());
            return;
        }
        if (!ActivityMgr.activityInShowTime(config.getActivityInfo())){
            getLogger().error("玩家在活动时间外使用冰雪游园皮肤,userId = {}",player.getUserId());
            return;
        }
        SnowGardenUserData userData = getSnowGardenUserDataOnlyGet(config.getActivityInfo().getActivityId(), player.getUserId());
        if (userData == null){
            getLogger().error("玩家使用冰雪游园皮肤数据不存在,userId = {}",player.getUserId());
            return;
        }

        int now = (int)(System.currentTimeMillis() / 1000);
        GoodsInfo goodsInfo = CommonMgr.getGoodsInfo(skinId);
        if (goodsInfo == null) {
            getLogger().error("SnowGardenMgr error on addDoll! GoodsInfo is null!");
            return;
        }
        SnowGardenDollConfig dollConfig = config.getSnowGardenDollConfig().get(skinId);
        if(null == dollConfig){
            getLogger().error("SnowGardenMgr error on addDoll! dollConfig is null!");
            return;
        }
        int limitTime = dollConfig.getTime();
        Map<Integer, SnowGardenSkinData> skinMap = userData.getSkinList();
        if (!skinMap.containsKey(skinId)){// 没有皮肤,直接给他设置
            SnowGardenSkinData newSkinData = new SnowGardenSkinData(skinId, limitTime, false);
            skinMap.put(skinId, newSkinData);
        } else {// 有皮肤且皮肤不是永久时，更新时间
            if (skinMap.containsKey(skinId) && skinMap.get(skinId).getLimitTime() != -1) {
                SnowGardenSkinData skinData = skinMap.get(skinId);
                // 加点时间
                int oldTime = skinData.getLimitTime();
                oldTime = oldTime < now ? now : oldTime;
                skinData.setLimitTime(oldTime + limitTime * count);
            }
        }
        synchronized (userData) {
            int nowPeriod = userData.getPeriod();
            int oldScore = userData.getPeriodScore(nowPeriod);
            int radio = goodsInfo.getParamList().get(0).intValue();
            int awardScore = (int) Math.ceil(oldScore * (radio / 1000.0));
            userData.addScore(nowPeriod, awardScore);

            userData.setUpdateOption();
        }

        player.getModule(SnowGardenModule.class).updateRank(userData, userData.getPeriod());
        player.getModule(SnowGardenModule.class).syncUserData();
    }

    /**
     * 计算皮肤 + 阶段加成（千分比）
     * @return
     */
    public static BigDecimal calcSkinRadio(Map<Integer, SnowGardenSkinData> skinDataMap, Map<Integer, SnowGardenMapData> indexData,int period){
        BigDecimal radio = BigDecimal.ZERO;
        SnowGardenConfig config = getSnowGardenConfig();
        for (int key : skinDataMap.keySet()) {
            GoodsInfo goodsInfo = CommonMgr.getGoodsInfo(key);
            String periodString = config.getSnowGardenDollConfig().get(key).getPeriod();
            List<Integer> periodList = StringUtils.stringToIntegerList(periodString, ";");
            if (periodList.contains(period)) {
//                radio += goodsInfo.getParamList().get(0).intValue();
                radio = radio.add(BigDecimal.valueOf(goodsInfo.getParamList().get(0).intValue()));
            }
        }
        BigDecimal levelRadio = BigDecimal.ZERO;
        if (period == eSnowGardenPeriodType.VISITOR_PERIOD.getType()) {
            levelRadio = levelRadio.add(BigDecimal.valueOf(SnowGardenMgr.getLevelRadio(indexData)));
        }
//        return ((radio + levelRadio)/ 1000) + 1.0;
        return radio.add(levelRadio).divide(BigDecimal.valueOf(1000)).add(BigDecimal.ONE);
    }

    /**
     * 获取阶段保底数
     */
    public static int randomGuarantee(int period) {
        int guarantee;
        SnowGardenConfig config = getSnowGardenConfig();
//        Random random = new Random();
        if (period == eSnowGardenPeriodType.UPGRADE_PERIOD.getType()) {// 一阶段
            // 保底选择最大
            int minParam1 = config.getCombMinParam1();
            int maxParam1 = config.getCombMaxParam1();
            if(minParam1 >= maxParam1){
                guarantee = minParam1;
            } else {
                guarantee = random.nextInt(maxParam1 - minParam1 + 1) + minParam1;
            }
        } else if(period == eSnowGardenPeriodType.VISITOR_PERIOD.getType()){
            // 保底选择最大
            int minParam2 = config.getCombMinParam2();
            int maxParam2 = config.getCombMaxParam2();
            if(minParam2 >= maxParam2){
                guarantee = maxParam2;
            } else {
                guarantee = random.nextInt(maxParam2 - minParam2 + 1) + minParam2;
            }
        } else {
            guarantee = 99999;
        }
        return guarantee;
    }

    // 2023/12/14 迭代，去除积分道具奖励
    public static Property getScoreAward(int period, int num){
        Property property = new Property();
        if (period == eSnowGardenPeriodType.UPGRADE_PERIOD.getType()){
            Property scoreAward = new Property(SnowGardenMgr.getSnowGardenConfig().getScore(), num);
            property.addProperty(scoreAward);
        } else if (period == eSnowGardenPeriodType.VISITOR_PERIOD.getType()){
            Property scoreAward = new Property(SnowGardenMgr.getSnowGardenConfig().getScore1(), num);
            property.addProperty(scoreAward);
        }
        return property;
    }

    /**
     * 获取阶段随机投掷模板
     */
    public static List<Integer> randomDice(int period) {
        List<Integer> resDice = new ArrayList<>();
        SnowGardenConfig config = getSnowGardenConfig();
//        Random random = new Random();
        // 看要不要给这个配置做个容错
        if (period == eSnowGardenPeriodType.UPGRADE_PERIOD.getType()) {// 一阶段
            List<List<Integer>> diceList = config.getDice1();
            if (diceList.size() <= 0) {
                return resDice;
            }
            int randomIndex = random.nextInt(diceList.size());
            return new ArrayList<>(diceList.get(randomIndex));
        } else if (period == eSnowGardenPeriodType.VISITOR_PERIOD.getType()) {
            List<List<Integer>> diceList = config.getDice2();
            if (diceList.size() <= 0) {
                return resDice;
            }
            int randomIndex = random.nextInt(diceList.size());
            return new ArrayList<>(diceList.get(randomIndex));
        }
        return resDice;
    }

    public static int visitPlayerEx(int activityId, long visitUserId, long visitServerId, int visitType, String visitParam, long targetUserId, long targetServerId, long recordTime) {
        UserInfo userInfo = UserMgr.getUserInfo(targetUserId);
        if (userInfo != null) {
            threadTaskManger.addTask(0, new SnowGardenVisitTask(activityId, visitUserId, visitServerId, visitType, visitParam, targetUserId, targetServerId, recordTime));
            return -1;
        } else {
            return GameErrorCode.E_USER_NO_FOUND;
        }
    }

    public static CrossUnionMember randomOneUnionMember(long userId, String unionId) {
        SnowGardenConfig config = getSnowGardenConfig();
        if (config == null) {
            return null;
        }
        Map<Long, CrossUnionMember> unionMemberMap = CrossUnionMgr.getUnionMemberMap(unionId);

        unionMemberMap.remove(userId);

        if (unionMemberMap.isEmpty()){
            return null;
        }

        ArrayList<CrossUnionMember> crossUnionMembers = new ArrayList<>();

        //防止导活动没覆盖到
        for (CrossUnionMember unionMember : unionMemberMap.values()) {
            if(config.getActivityInfo().getServerIdList().contains(unionMember.getServerId())){
                crossUnionMembers.add(unionMember);
            }
        }

        if (crossUnionMembers.isEmpty()){
            return null;
        }

        //随机一个
//        Random random = new Random();
        int index = random.nextInt(crossUnionMembers.size());
        return crossUnionMembers.get(index);
    }

    // 根据阶段获取投掷奖励
    public static Property getRollReward(int period) {
        if (period == eSnowGardenPeriodType.UPGRADE_PERIOD.getType()) {
            return PropertyHelper.randomPropertyByListList(snowGardenConfig.getRollRewardList());
        } else if (period == eSnowGardenPeriodType.VISITOR_PERIOD.getType()) {
            return PropertyHelper.randomPropertyByListList(snowGardenConfig.getRollRewardList2());
        }
        return new Property();
    }

    public static void changePeriod(int nowPeriod, SnowGardenUserData userData) {
        if (nowPeriod != -1 && nowPeriod != userData.getPeriod()) {
            // 阶段转换
            synchronized (userData) {
                userData.setPeriod(nowPeriod);
                userData.setCombList(new ArrayList<>());
//            userData.setScore(0);
                // 累计步数也重置
                userData.setLoopNum(0);
                userData.setResultList(SnowGardenMgr.initResultList());
                userData.setGuarantee(SnowGardenMgr.randomGuarantee(nowPeriod));
                // 切换成默认皮肤
                int initSuitId = SnowGardenMgr.getSnowGardenConfig().getInitSuitId();
                userData.setSuit(initSuitId);
                userData.setDice(SnowGardenMgr.randomDice(nowPeriod));
                userData.setRecharge(false);
                userData.setUpdateOption();
            }
        }
    }

    /**
     * 别人拜访我,在单线程任务里跑,不会并发
     *
     * @param visitUserId
     * @param visitServerId
     * @param visitType
     * @param visitParam
     * @param targetUserId
     * @param targetServerId
     * @param recordTime
     * @return
     */
    public static int crossOffLineVisit(long visitUserId, long visitServerId, int visitType, String visitParam, long targetUserId, long targetServerId, long recordTime) {
        SnowGardenConfig config = SnowGardenMgr.getSnowGardenConfig();
        if (config == null) {
            return GameErrorCode.E_ACTIVITY_NOT_OPEN;
        }
        int activityId = config.getActivityInfo().getActivityId();
        UserBaseInfo userBase = UserMgr.getUserBaseInfo(targetUserId, targetServerId);
        if (userBase == null) {
            return GameErrorCode.E_USER_NO_FOUND;
        }
        int period = SnowGardenMgr.calcNowPeriod();

        if (visitType != eSnowGardenRequestVisitType.BUILDING.getType() && visitType != eSnowGardenRequestVisitType.INVITED.getType()) {
            SnowGardenUserData snowGardenUserDataOnlyGet = SnowGardenMgr.getSnowGardenUserDataOnlyGet(activityId, targetUserId);
            if (snowGardenUserDataOnlyGet == null) {
                snowGardenUserDataOnlyGet = createUserData(targetUserId);//这里拼数据用,不入库
            }
            // 非指定上述类型拜访则不需要记录拜访数据,下发数据后返回
            SnowGardenProto.SnowGardenToCrossVisitRespMsg.Builder builder = SnowGardenProto.SnowGardenToCrossVisitRespMsg.newBuilder();
            builder.setActivityId(activityId);
            builder.setRet(0);
            builder.setUserId(visitUserId);
            builder.setUserServerId(visitServerId);
            builder.setUserData(PlayerBasePb.parsePlayerBaseTempMsg(userBase));
            SnowGardenProto.VisitOtherSnowGardenTemp.Builder userBuilder = SnowGardenPb.parseVisitOtherSnowGardenTemp(snowGardenUserDataOnlyGet);
            builder.setUserActData(userBuilder);
            builder.setVisitResult("");
            builder.setVisitedUserId(targetUserId);
            builder.setRecordTime(recordTime);
            // 发到跨服
            GamePlayerMgr.sendPacket(0, YanQuMessageUtils.buildMessage(CrossProtocol.C_SNOW_GARDEN_VISITED_RESP, builder));
            return 0;
        }

        SnowGardenUserData visitUserData = getSnowGardenUserDataNewIfNull(config.getActivityInfo().getActivityId(), targetUserId);
        if (visitUserData == null) {
            return GameErrorCode.E_USER_NO_FOUND;
        }
        int recordId;
        String result;
        int realAwardScore = 0;
        synchronized (visitUserData) {
            changePeriod(period, visitUserData);
            if (visitType == eSnowGardenRequestVisitType.BUILDING.getType()) {
                BigDecimal skinRadio = SnowGardenMgr.calcSkinRadio(visitUserData.getSkinList(), visitUserData.getIndexData(), period);
                // 升级建筑 参数  地块_升级等级_拜访者获得积分
                List<Integer> paramList = StringUtils.stringToIntegerList(visitParam, "_");
                recordId = paramList.get(0);
                int randomStatue = SnowGardenMgr.getSnowGardenConfig().getSnowGardenMapConfig().get(recordId).getStatueId();
                int oldLevel = visitUserData.getIndexData().get(recordId).getLevel();
                // 升级建筑 + 积分
                int newLevel = oldLevel + paramList.get(1);
                visitUserData.getIndexData().get(recordId).setLevel(newLevel);
                int paramScore = SnowGardenMgr.getSnowGardenConfig().getSnowGardenStatueConfig().get(randomStatue).getScore() * paramList.get(1);
                realAwardScore = BigDecimal.valueOf(paramScore).multiply(skinRadio).setScale(0, RoundingMode.CEILING).intValue();
                result = String.format("%d_%d_%d", recordId, newLevel, paramList.get(2));
            } else if (visitType == eSnowGardenRequestVisitType.INVITED.getType()) {
                BigDecimal skinRadio = SnowGardenMgr.calcSkinRadio(visitUserData.getSkinList(), visitUserData.getIndexData(), period);
                // 邀请 参数  游客id_积分倍率_拜访者获得积分
                List<Integer> paramList = StringUtils.stringToIntegerList(visitParam, "_");
                recordId = paramList.get(0);
                visitUserData.addInviteNum(1);
                int paramScore = SnowGardenMgr.getVisitorScoreById(recordId) * paramList.get(1);
                realAwardScore = BigDecimal.valueOf(paramScore).multiply(skinRadio).setScale(0, RoundingMode.CEILING).intValue();
                visitUserData.getInvitedIdList().add(recordId);
                result = String.format("%d_%d", recordId, paramList.get(2));
            } else {
                return GameErrorCode.E_ERROR_DATA;
            }
            visitUserData.addScore(period, realAwardScore);
        }

        // 优化：一二阶段积分拆分
        if (visitUserData.getPeriod() == eSnowGardenPeriodType.UPGRADE_PERIOD.getType()) {
            ActivityRankMgr.changeActivityRank(visitUserData.getUserId(), activityId, eGamePlayerEventType.SnowGardenScoreRank.getValue(),
                    BigInteger.valueOf(visitUserData.getScore()), "");
        } else if (visitUserData.getPeriod() == eSnowGardenPeriodType.VISITOR_PERIOD.getType()) {
            ActivityRankMgr.changeActivityRank(visitUserData.getUserId(), activityId, eGamePlayerEventType.SnowGardenSecondScoreRank.getValue(),
                    BigInteger.valueOf(visitUserData.getSecondScore()), "");
        }

        //成就改成登录时同步一下
        //更新我的来访列表
        getCacheSnowDataActivity(activityId).addCacheVisitRecord(activityId, targetUserId, visitUserId, eSnowGardenVisitType.VISIT_TYPE_VISITED_ME.getType(), recordId, realAwardScore, visitUserData.getPeriod());

        SnowGardenProto.SnowGardenToCrossVisitRespMsg.Builder builder = SnowGardenProto.SnowGardenToCrossVisitRespMsg.newBuilder();
        builder.setActivityId(activityId);
        builder.setRet(0);
        builder.setUserId(visitUserId);
        builder.setUserServerId(visitServerId);
        builder.setUserData(PlayerBasePb.parsePlayerBaseTempMsg(userBase));
        SnowGardenProto.VisitOtherSnowGardenTemp.Builder userBuilder = SnowGardenPb.parseVisitOtherSnowGardenTemp(visitUserData);
        builder.setUserActData(userBuilder);
        builder.setVisitResult(result);
        builder.setVisitedUserId(targetUserId);
        builder.setRecordTime(recordTime);
        // 发到跨服
        GamePlayerMgr.sendPacket(0, YanQuMessageUtils.buildMessage(CrossProtocol.C_SNOW_GARDEN_VISITED_RESP, builder));
        return 0;
    }

    public static List<UserSnowGardenVisitRecord> popCacheVisitRecordData(int activityId, long userId) {
        CacheSnowDataActivity cacheSnowDataActivity = cacheSnowDataActivityMap.get(activityId);
        if (null == cacheSnowDataActivity) {
            return null;
        }

        return cacheSnowDataActivity.popCacheVisitRecordData(userId);
    }

    public static SnowGardenUserData getSnowGardenUserDataNewIfNull(int activityId, long userId) {
        CacheSnowDataActivity activity = getCacheSnowDataActivity(activityId);
        if (activity == null) {
            return null;
        }
        return activity.getSnowGardenUserDataNewIfNull(activityId, userId);
    }

    public static SnowGardenUserData getSnowGardenUserDataOnlyGet(int activityId, long userId) {
        CacheSnowDataActivity activity = getCacheSnowDataActivity(activityId);
        if (activity == null) {
            return null;
        }
        return activity.getSnowGardenUserDataOnlyGet(userId);
    }

    // 判断3格是否满足全等
    public static boolean checkComb(List<Integer> resultList, int place1, int place2, int place3) {
        return resultList.get(place1).equals(resultList.get(place2)) && resultList.get(place2).equals(resultList.get(place3));
    }

    /**
     * 判断九宫格组合反应
     *
     * @param resultList 内部集合
     * @param addValue   加入的值
     * @return
     */
    public static SnowGardenResultCombData calcResultComb(List<Integer> resultList, int addValue) {
        SnowGardenResultCombData snowGardenResultCombData = new SnowGardenResultCombData();
        // 先塞进列表
        for (int i = 0; i < SnowGardenMgr.getResultNum(); i++) {
            if (resultList.get(i) == 0) {
                resultList.set(i, addValue);
                break;
            }
        }
        // 深拷贝一份数据
        List<Integer> newResultList = new ArrayList<>();
        for (int i = 0; i < SnowGardenMgr.getResultNum(); i++) {
            newResultList.add(i, resultList.get(i));
        }
        int combCount = 0;
        // 判断组合(同时触发)
        if (resultList.get(0) != 0) {
            if (checkComb(resultList, 0, 1, 2)) {
                newResultList.set(0, 0);
                newResultList.set(1, 0);
                newResultList.set(2, 0);
                combCount++;
            }
            if (checkComb(resultList, 0, 3, 6)) {
                newResultList.set(0, 0);
                newResultList.set(3, 0);
                newResultList.set(6, 0);
                combCount++;
            }
        }
        if (resultList.get(4) != 0) {
            if (checkComb(resultList, 0, 4, 8)) {
                newResultList.set(0, 0);
                newResultList.set(4, 0);
                newResultList.set(8, 0);
                combCount++;
            }
            if (checkComb(resultList, 2, 4, 6)) {
                newResultList.set(2, 0);
                newResultList.set(4, 0);
                newResultList.set(6, 0);
                combCount++;
            }
            if (checkComb(resultList, 1, 4, 7)) {
                newResultList.set(1, 0);
                newResultList.set(4, 0);
                newResultList.set(7, 0);
                combCount++;
            }
            if (checkComb(resultList, 3, 4, 5)) {
                newResultList.set(3, 0);
                newResultList.set(4, 0);
                newResultList.set(5, 0);
                combCount++;
            }
        }
        if (resultList.get(8) != 0) {
            if (checkComb(resultList, 2, 5, 8)) {
                newResultList.set(2, 0);
                newResultList.set(5, 0);
                newResultList.set(8, 0);
                combCount++;
            }
            if (checkComb(resultList, 6, 7, 8)) {
                newResultList.set(6, 0);
                newResultList.set(7, 0);
                newResultList.set(8, 0);
                combCount++;
            }
        }

        // 如果塞满了就清除
        boolean hasEmpty = false;
        for (int i = 0; i < newResultList.size(); i++) {
            if (newResultList.get(i) == 0) {
                hasEmpty = true;
                break;
            }
        }
        newResultList = hasEmpty ? newResultList : SnowGardenMgr.initResultList();
        snowGardenResultCombData.setResultList(newResultList);
        snowGardenResultCombData.setCombCount(combCount);
        return snowGardenResultCombData;
    }

    /** 随机阶段投掷数
     *
     * @param rollNum
     * @return
     */
    public static int randomOneStep(int rollNum, List<Integer> numberList, int drawTimes, SnowGardenUserData data) {
        int randomNum = 0;
        if (data.getDice().size() > 0) {// 还有随机模板没跑完？
            randomNum = data.getDice().remove(0);
            return randomNum;
        }

        if (numberList.size() > 0){
            return numberList.get(numberList.size() - drawTimes);
        }

        // 保底修改随机值
        if (data.getGuarantee() <= 0) {
            int copyOneNum = 0;
            for (int res : data.getResultList()) {
                if (res > 0) {
                    copyOneNum = res;
                    break;
                }
            }
            // 结果列表为空就按照随机值来
            if (copyOneNum > 0){
                return copyOneNum;
            }
        }

        randomNum = random.nextInt(rollNum) + 1;
        return randomNum;
    }

    // 随机地块
    public static int initIndexId() {
        SnowGardenConfig config = SnowGardenMgr.getSnowGardenConfig();
        Map<Integer, SnowGardenMapConfig> map = config.getSnowGardenMapConfig();
        List<Integer> randomIndex = new ArrayList<>();
        for (int index : map.keySet()) {
            if (map.get(index).getType() == eSnowGardenMapType.LONG_PLOT.getType()) {
                randomIndex.add(index);
            }
        }
//        Random r = new Random();
        int randomNum = random.nextInt(randomIndex.size());
        return randomIndex.get(randomNum);
    }

    // 随机游客
    public static int initVisitorId(){
        Map<Integer, SnowGardenVisitorConfig> snowGardenVisitorConfig = SnowGardenMgr.getSnowGardenConfig().getSnowGardenVisitorConfig();
        List<Integer> randomVisitorIdList = new ArrayList<>();
        randomVisitorIdList.addAll(snowGardenVisitorConfig.keySet());
//        Random random = new Random();
        int randomIndex = random.nextInt(randomVisitorIdList.size());
        return randomVisitorIdList.get(randomIndex);
    }
}

